# 拉取 go1.20 alpine 镜像 并作为 builder 镜像
FROM golang:1.20-alpine AS builder
# 换源 把 APK 源换为中国科技大学镜像源 用 set 命令保证命令执行，出错会直接退出而不会继续执行下面命令
RUN set -eux && sed -i 's/dl-cdn.alpinelinux.org/mirrors.ustc.edu.cn/g' /etc/apk/repositories
# 待编译的文件路径
ARG APP_RELATIVE_PATH=./cmd/server
# 配置文件 prod.yaml 还是 local.yaml
ARG APP_CONF=local.yml

# 复制整个项目 .dockerignore 可以指定不需要复制的文件
COPY . /data/app
# 工作目录
WORKDIR /data/app

# 清理 bin 目录
RUN rm -rf /data/app/bin/
# 下载依赖项并编译 -ldflags="-s -w"选项用于优化二进制文件大小，去除符号和调试信息 -o指定编译后的二进制文件名
RUN export GOPROXY=https://goproxy.cn,direct && go mod tidy && go build -ldflags="-s -w" -o ./bin/server ${APP_RELATIVE_PATH}
# 移动配置文件 让可执行文件和配置文件放在正确的目录下
COPY ./config/${APP_CONF} /data/app/bin/config/${APP_CONF}

# 多阶段构建 使用 alpine 作为最终镜像
FROM alpine:3.16
# 同上 换源
RUN set -eux && sed -i 's/dl-cdn.alpinelinux.org/mirrors.ustc.edu.cn/g' /etc/apk/repositories

# 安装时区数据包 设置时区为 "亚洲/上海" 把数据包复制后 删除其他不需要的数据包
RUN apk add tzdata && cp /usr/share/zoneinfo/Asia/Shanghai /etc/localtime \
    && echo "Asia/Shanghai" > /etc/timezone \
    && apk del tzdata

# 指定环境变量 比如开发环境、测试环境、生产环境
ARG APP_ENV=local
# 环境变量 用 ENV 定义的变量在容器启动后依然可使用
ENV APP_ENV=${APP_ENV}

# 工作目录
WORKDIR /data/app
# 把 builder 镜像的编译后的二进制文件 复制到当前镜像的 /data/app 目录下
COPY --from=builder /data/app/bin /data/app

# 暴露端口
EXPOSE 8000
# 启动容器后运行可执行文件
ENTRYPOINT [ "./server" ]

# 示例命令
# docker build -t smartlibrary:v1 .
# docker run -d --name smartlibrary -p 8000:8000 --restart unless-stopped smartlibrary:v1